package com.zhijian.medical.util.redis;

import cn.hutool.core.date.DateUtil;
import com.zhijian.medical.entity.po.RoutinePathologyRs;
import com.zhijian.medical.entity.po.RoutinePathologyTs;
import com.zhijian.medical.entity.vo.request.RoutinePathologyRsSearchVo;
import com.zhijian.medical.entity.vo.request.RoutinePathologyTsSearchVo;
import com.zhijian.medical.entity.vo.response.RoutinePathologyRsVo;
import com.zhijian.medical.entity.vo.response.RoutinePathologyTsVo;
import com.zhijian.medical.enums.RoutineRsEnum;
import com.zhijian.medical.enums.RoutineTsEnum;
import com.zhijian.medical.service.CacheService;
import com.zhijian.medical.service.RoutinePathologyRsService;
import com.zhijian.medical.service.RoutinePathologyTsService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;
import redis.clients.jedis.JedisPubSub;

import java.util.Date;

/**
 * 接收过期信息
 */
@Transactional
@Component
public class RedisKeyExpirationListener extends JedisPubSub {

    @Autowired
    private CacheService cacheService;
    @Autowired
    private RoutinePathologyTsService tsService;
    @Autowired
    private RoutinePathologyRsService rsService;

    @Override
    public void onPMessage(String pattern, String channel, String message) {
//        System.out.println("接收到键过期事件：pattern=" + pattern + ", channel=" + channel + ", message=" + message);
        // 这里可以添加处理键过期的逻辑

        // 根据脱水框编号记录脱水开始时间,key是 gl_step_ts_time/脱水框编号/时间
        if (message.startsWith("gl_step_ts_time")) {
            String[] split = message.split("/");
            if (split.length == 2) {
                //脱水框编号
                String tsCode = split[1];
                // 获取现在的脱水数据
                RoutinePathologyTsVo tsVo = tsService.selectOne(RoutinePathologyTsSearchVo.builder().sample(tsCode).build());
                // 更新状态
                tsService.updateByPrimaryKeySelective(RoutinePathologyTs.builder()
                                .id(tsVo.getId())
                                .step(nextTsStep(tsVo.getStep(), tsCode))
                                .build());
            }
        } else if (message.startsWith("gl_step_rs_time")) {
            String[] split = message.split("/");
            if (split.length == 2) {
                //染色架编号
                String tsCode = split[1];
                // 获取现在的染色数据
                RoutinePathologyRsVo tsVo = rsService.selectOne(RoutinePathologyRsSearchVo.builder().sample(tsCode).build());
                // 更新状态
                rsService.updateByPrimaryKeySelective(RoutinePathologyRs.builder()
                        .id(tsVo.getId())
                        .step(nextRsStep(tsVo.getStep(), tsCode))
                        .build());
            }
        }
    }

    // 当订阅模式时触发
    @Override
    public void onPSubscribe(String pattern, int subscribedChannels) {
        System.out.println("订阅模式：" + pattern + ", 订阅的通道数量：" + subscribedChannels);
    }

    // 当取消订阅模式时触发
    @Override
    public void onPUnsubscribe(String pattern, int subscribedChannels) {
        System.out.println("取消订阅模式：" + pattern + ", 当前订阅的通道数量：" + subscribedChannels);
    }

    /**
     * 返回脱水下一步流程，重新设置 redis 倒计时
     * @param setp
     * @return
     */
    private Byte nextTsStep(Byte setp, String numbers) {
        // 计算下一步骤
        // 脱水流程共 14小时：10%甲醛（2小时）、80%乙醇（3小时）、95%乙醇①（2小时）、95%乙醇②（1小时）、无水乙醇①（1小时）、
        // 无水乙醇②（1小时）、二甲苯①（0.5小时）、二甲苯②（0.5小时）、石蜡①（1小时）、石蜡②（1小时）、石蜡③（1小时）
        byte stepByte ;
        int leftTime = 1;
        if (setp == null) {
            stepByte = RoutineTsEnum.OVER.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.JQ.getCode().byteValue())) {
//            leftTime = 3 * 60 * 60;
            leftTime = 6;
            stepByte = RoutineTsEnum.YC.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.YC.getCode().byteValue())) {
            leftTime = 6;
//            leftTime = 2 * 60 * 60;
            stepByte = RoutineTsEnum.YC_ONE.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.YC_ONE.getCode().byteValue())) {
//            leftTime = 1 * 60 * 60;
            leftTime = 6;
            stepByte = RoutineTsEnum.YC_TWO.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.YC_TWO.getCode().byteValue())) {
//            leftTime = 1 * 60 * 60;
            leftTime = 6;
            stepByte = RoutineTsEnum.WSYC_ONE.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.WSYC_ONE.getCode().byteValue())) {
//            leftTime = 1 * 60 * 60;
            leftTime = 6;
            stepByte = RoutineTsEnum.WSYC_TWO.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.WSYC_TWO.getCode().byteValue())) {
//            leftTime = 1 * 30 * 60;
            leftTime = 6;
            stepByte = RoutineTsEnum.EJB_ONE.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.EJB_ONE.getCode().byteValue())) {
//            leftTime = 1 * 30 * 60;
            leftTime = 5;
            stepByte = RoutineTsEnum.EJB_TWO.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.EJB_TWO.getCode().byteValue())) {
//            leftTime = 1 * 60 * 60;
            leftTime = 5;
            stepByte = RoutineTsEnum.SL_ONE.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.SL_ONE.getCode().byteValue())) {
//            leftTime = 1 * 60 * 60;
            leftTime = 5;
            stepByte = RoutineTsEnum.SL_TWO.getCode().byteValue();
        } else if (setp.equals(RoutineTsEnum.SL_TWO.getCode().byteValue())) {
//            leftTime = 1 * 60 * 60;
            leftTime = 5;
            stepByte = RoutineTsEnum.SL_THREE.getCode().byteValue();
        } else {
            // 最后一步不需要设置 redis
            return RoutineTsEnum.OVER.getCode().byteValue();
        }
        cacheService.setex("gl_step_ts_time/" + numbers, leftTime, "1");
        return stepByte;
    }

    /**
     * 返回染色下一步流程，重新设置 redis 倒计时
     * @param step
     * @return
     */
    private Byte nextRsStep(Byte step, String numbers) {
        // 计算下一步骤
        // 染色流程包括：
//        1、二甲苯①，10min；
//        2、二甲苯②，10min；
//        3、无水乙醇①，1min；
//        4、无水乙醇②，1min；
//        5、95%乙醇①，1min；
//        6、95%乙醇②，1min；
//        7、80%乙醇①，1min；
//        8、80%乙醇②，1min；
//        9、自来水洗，1min；
//        10、苏木素，2min；
//        11、自来水洗，1min；
//        12、1%盐酸酒精，30s；
//        13、自来水洗，5min；
//        14、伊红，1min；
//        15、自来水洗，30s；
//        16、85%乙醇，20s；
//        17、90%乙醇，30s；
//        18、95%乙醇①，1min；
//        19、95%乙醇②，1min；
//        20、无水乙醇①，2min；
//        21、无水乙醇②，2min；
//        22、二甲苯①，2min；
//        23、二甲苯②，2min；
//        24、封片，5min。
        byte stepByte ;
        int leftTime = 1;
        if (step == null) {
            stepByte = RoutineRsEnum.OVER.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.ONE.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.TWO.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.TWO.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.THREE.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.THREE.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.FOUR.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.FOUR.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.FIVE.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.FIVE.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.SIX.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.SIX.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.SEVEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.SEVEN.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.EIGHT.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.EIGHT.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.NINE.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.NINE.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.TEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.TEN.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.ELEVEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.ELEVEN.getCode().byteValue())) {
            leftTime = 1 * 30;
            stepByte = RoutineRsEnum.TWELVE.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.TWELVE.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.THIRTEEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.THIRTEEN.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.FOURTEEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.FOURTEEN.getCode().byteValue())) {
            leftTime = 1 * 30;
            stepByte = RoutineRsEnum.FIFTEEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.FIFTEEN.getCode().byteValue())) {
            leftTime = 1 * 20;
            stepByte = RoutineRsEnum.SIXTEEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.SIXTEEN.getCode().byteValue())) {
            leftTime = 1 * 30;
            stepByte = RoutineRsEnum.SEVENTEEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.SEVENTEEN.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.EIGHTEEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.EIGHTEEN.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.NINETEEN.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.NINETEEN.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.TWENTY.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.TWENTY.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.TWENTY_ONE.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.TWENTY_ONE.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.TWENTY_TWO.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.TWENTY_TWO.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.TWENTY_THREE.getCode().byteValue();
        } else if (step.equals(RoutineRsEnum.TWENTY_THREE.getCode().byteValue())) {
            leftTime = 1 * 60;
            stepByte = RoutineRsEnum.TWENTY_FOUR.getCode().byteValue();
        } else {
            // 最后一步不需要设置 redis
            return RoutineRsEnum.OVER.getCode().byteValue();
        }
        cacheService.setex("gl_step_rs_time/" + numbers, leftTime, "1");
        return stepByte;
    }
}
